using System.ComponentModel;
using System.Globalization;
using System.Runtime.Versioning;
using System.Security;
using System.Text.RegularExpressions;

using ColumnizerLib;

using LogExpert.Core.Classes.Highlight;
using LogExpert.Core.Entities;
using LogExpert.Core.Helpers;
using LogExpert.Core.Interface;
using LogExpert.UI.Controls;
using LogExpert.UI.Dialogs;
using LogExpert.UI.Entities;

namespace LogExpert.Dialogs;

[SupportedOSPlatform("windows")]
internal partial class HighlightDialog : Form
{
    #region Private Fields

    private readonly Image _applyButtonImage;
    private string _bookmarkComment;
    private ActionEntry _currentActionEntry = new();
    private HighlightGroup _currentGroup;
    private List<HighlightGroup> _highlightGroupList;

    #endregion

    #region Ctor

    public HighlightDialog (IConfigManager configManager)
    {
        SuspendLayout();

        AutoScaleDimensions = new SizeF(96F, 96F);
        AutoScaleMode = AutoScaleMode.Dpi;

        InitializeComponent();

        ApplyResources();

        ConfigManager = configManager;
        Load += OnHighlightDialogLoad;
        listBoxHighlight.DrawItem += OnHighlightListBoxDrawItem;
        _applyButtonImage = btnApply.Image;
        btnApply.Image = null;

        ResumeLayout();
    }

    private void ApplyResources ()
    {
        // Dialog
        Text = Resources.HighlightDialog_UI_Title;

        btnOk.Text = Resources.LogExpert_Common_UI_Button_OK;
        btnCancel.Text = Resources.LogExpert_Common_UI_Button_Cancel;
        btnAdd.Text = Resources.LogExpert_Common_UI_Button_Add;
        btnDelete.Text = Resources.LogExpert_Common_UI_Button_Delete;
        btnMoveUp.Text = Resources.LogExpert_Common_UI_Button_MoveUp;
        btnMoveDown.Text = Resources.LogExpert_Common_UI_Button_MoveDown;
        btnApply.Text = Resources.LogExpert_Common_UI_Button_Apply;
        btnCustomForeColor.Text = Resources.HighlightDialog_UI_Button_CustomForeColor;
        btnCustomBackColor.Text = Resources.HighlightDialog_UI_Button_CustomBackColor;
        btnBookmarkComment.Text = Resources.HighlightDialog_UI_Button_BookmarkComment;
        btnSelectPlugin.Text = Resources.HighlightDialog_UI_Button_SelectPlugin;
        btnImportGroup.Text = Resources.LogExpert_Common_UI_Button_Import;
        btnExportGroup.Text = Resources.LogExpert_Common_UI_Button_Export;
        btnMoveGroupDown.Text = Resources.HighlightDialog_UI_Button_GroupDown;
        btnMoveGroupUp.Text = Resources.HighlightDialog_UI_Button_GroupUp;
        btnCopyGroup.Text = Resources.HighlightDialog_UI_Button_Copy;
        btnDeleteGroup.Text = Resources.HighlightDialog_UI_Button_DeleteGroup;
        btnNewGroup.Text = Resources.HighlightDialog_UI_Button_NewGroup;

        labelForgroundColor.Text = Resources.HighlightDialog_UI_Label_ForegroundColor;
        labelBackgroundColor.Text = Resources.HighlightDialog_UI_Label_BackgroundColor;
        labelSearchString.Text = Resources.HighlightDialog_UI_Label_SearchString;
        labelAssignNamesToGroups.Text = Resources.HighlightDialog_UI_Label_AssignNamesToGroups;

        checkBoxRegex.Text = Resources.HighlightDialog_UI_CheckBox_RegEx;
        checkBoxCaseSensitive.Text = Resources.HighlightDialog_UI_CheckBox_CaseSensitive;
        checkBoxDontDirtyLed.Text = Resources.HighlightDialog_UI_CheckBox_DontDirtyLed;
        checkBoxBookmark.Text = Resources.HighlightDialog_UI_CheckBox_Bookmark;
        checkBoxStopTail.Text = Resources.HighlightDialog_UI_CheckBox_StopTail;
        checkBoxPlugin.Text = Resources.HighlightDialog_UI_CheckBox_Plugin;
        checkBoxWordMatch.Text = Resources.HighlightDialog_UI_CheckBox_WordMatch;
        checkBoxBold.Text = Resources.HighlightDialog_UI_CheckBox_Bold;
        checkBoxNoBackground.Text = Resources.HighlightDialog_UI_CheckBox_NoBackground;

        groupBoxLineMatchCriteria.Text = Resources.HighlightDialog_UI_GroupBox_LineMatchCriteria;
        groupBoxColoring.Text = Resources.HighlightDialog_UI_GroupBox_Coloring;
        groupBoxActions.Text = Resources.HighlightDialog_UI_GroupBox_Actions;
        groupBoxGroups.Text = Resources.HighlightDialog_UI_GroupBox_Groups;
    }

    #endregion

    #region Properties / Indexers

    [DesignerSerializationVisibility(DesignerSerializationVisibility.Visible)]
    public List<HighlightGroup> HighlightGroupList
    {
        get => _highlightGroupList;
        set
        {
            _highlightGroupList ??= [];

            foreach (var group in value)
            {
                _highlightGroupList.Add((HighlightGroup)group.Clone());
            }
        }
    }

    [DesignerSerializationVisibility(DesignerSerializationVisibility.Visible)]
    public IList<IKeywordAction> KeywordActionList { get; set; }

    [DesignerSerializationVisibility(DesignerSerializationVisibility.Visible)]
    public string PreSelectedGroupName { get; set; }

    private bool IsDirty => btnApply.Image == _applyButtonImage;

    private IConfigManager ConfigManager { get; }

    #endregion

    #region Event handling Methods

    private void OnAddButtonClick (object sender, EventArgs e)
    {
        AddNewEntry();
        Dirty();
    }

    private void OnBtnApplyClick (object sender, EventArgs e)
    {
        SaveEntry();
    }

    private void OnBtnBookmarkCommentClick (object sender, EventArgs e)
    {
        BookmarkCommentDlg dlg = new()
        {
            Comment = _bookmarkComment
        };

        if (dlg.ShowDialog() == DialogResult.OK)
        {
            _bookmarkComment = dlg.Comment;
            Dirty();
        }
    }

    private void OnBtnCopyGroupClick (object sender, EventArgs e)
    {
        if (comboBoxGroups.SelectedIndex >= 0 && comboBoxGroups.SelectedIndex < HighlightGroupList.Count)
        {
            var newGroup = (HighlightGroup)HighlightGroupList[comboBoxGroups.SelectedIndex].Clone();
            newGroup.GroupName = $"{Resources.HighlightDialog_UI_Snippet_CopyOf} {newGroup.GroupName}";

            HighlightGroupList.Add(newGroup);
            FillGroupComboBox();
            SelectGroup(HighlightGroupList.Count - 1);
        }
    }

    private void OnBtnCustomBackColorClick (object sender, EventArgs e)
    {
        ChooseColor(colorBoxBackground);
        Dirty();
    }

    private void OnBtnCustomForeColorClick (object sender, EventArgs e)
    {
        ChooseColor(colorBoxForeground);
        Dirty();
    }

    private void OnBtnDelGroupClick (object sender, EventArgs e)
    {
        // the last group cannot be deleted
        if (HighlightGroupList.Count == 1)
        {
            return;
        }

        if (comboBoxGroups.SelectedIndex >= 0 && comboBoxGroups.SelectedIndex < HighlightGroupList.Count)
        {
            var index = comboBoxGroups.SelectedIndex;
            HighlightGroupList.RemoveAt(comboBoxGroups.SelectedIndex);
            FillGroupComboBox();
            if (index < HighlightGroupList.Count)
            {
                SelectGroup(index);
            }
            else
            {
                SelectGroup(HighlightGroupList.Count - 1);
            }
        }
    }

    //TODO: This class should not knoow ConfigManager?
    private void OnBtnExportGroupClick (object sender, EventArgs e)
    {
        SaveFileDialog dlg = new()
        {
            Title = Resources.HighlightDialog_UI_Title_ExportSettings,
            DefaultExt = "json",
            AddExtension = true,
            Filter = Resources.HighlightDialog_UI_Export_Filter
        };

        if (dlg.ShowDialog() == DialogResult.OK)
        {
            FileInfo fileInfo = new(dlg.FileName);
            ConfigManager.Export(fileInfo, Core.Config.SettingsFlags.HighlightSettings);
        }
    }

    private void OnBtnGroupDownClick (object sender, EventArgs e)
    {
        var index = comboBoxGroups.SelectedIndex;
        if (index > -1 && index < _highlightGroupList.Count - 1)
        {
            _highlightGroupList.Reverse(index, 2);
            comboBoxGroups.Refresh();
            FillGroupComboBox();
            SelectGroup(index + 1);
        }
    }

    private void OnBtnGroupUpClick (object sender, EventArgs e)
    {
        var index = comboBoxGroups.SelectedIndex;
        if (index > 0)
        {
            _highlightGroupList.Reverse(index - 1, 2);
            comboBoxGroups.Refresh();
            FillGroupComboBox();
            SelectGroup(index - 1);
        }
    }

    private void OnBtnImportGroupClick (object sender, EventArgs e)
    {
        ImportSettingsDialog dlg = new(Core.Config.ExportImportFlags.HighlightSettings);

        foreach (Control ctl in dlg.groupBoxImportOptions.Controls)
        {
            if (ctl.Tag != null)
            {
                ((CheckBox)ctl).Checked = false;
            }
        }

        dlg.checkBoxHighlightSettings.Checked = true;
        dlg.checkBoxKeepExistingSettings.Checked = true;

        if (dlg.ShowDialog() != DialogResult.OK)
        {
            return;
        }

        if (string.IsNullOrWhiteSpace(dlg.FileName))
        {
            return;
        }

        Cursor.Current = Cursors.WaitCursor;

        FileInfo fileInfo;

        try
        {
            fileInfo = new FileInfo(dlg.FileName);
        }
        catch (Exception ex) when (ex is ArgumentNullException
                                    or SecurityException
                                    or ArgumentException
                                    or UnauthorizedAccessException
                                    or PathTooLongException
                                    or NotSupportedException)
        {
            _ = MessageBox.Show(this, Resources.HighlightDialog_UI_SettingsCouldNotBeImported, Resources.LogExpert_Common_UI_Title_LogExpert);
            return;
        }

        ConfigManager.ImportHighlightSettings(fileInfo, dlg.ImportFlags);
        Cursor.Current = Cursors.Default;

        _highlightGroupList = ConfigManager.Settings.Preferences.HighlightGroupList;

        FillGroupComboBox();

        _ = MessageBox.Show(this, Resources.HighlightDialog_UI_SettingsImported, Resources.LogExpert_Common_UI_Title_LogExpert);

    }

    private void OnBtnMoveDownClick (object sender, EventArgs e)
    {
        var index = listBoxHighlight.SelectedIndex;

        if (index > -1 && index < listBoxHighlight.Items.Count - 1)
        {
            var item = listBoxHighlight.SelectedItem;
            listBoxHighlight.Items.RemoveAt(index);
            listBoxHighlight.Items.Insert(index + 1, item);
            listBoxHighlight.SelectedIndex = index + 1;
            _currentGroup.HighlightEntryList.Reverse(index, 2);
        }
    }

    private void OnBtnMoveUpClick (object sender, EventArgs e)
    {
        var index = listBoxHighlight.SelectedIndex;
        if (index > 0)
        {
            var item = listBoxHighlight.SelectedItem;
            listBoxHighlight.Items.RemoveAt(index); // will also clear the selection
            listBoxHighlight.Items.Insert(index - 1, item);
            listBoxHighlight.SelectedIndex = index - 1; // restore the selection
            _currentGroup.HighlightEntryList.Reverse(index - 1, 2);
        }
    }

    private void OnBtnNewGroupClick (object sender, EventArgs e)
    {
        // Propose a unique name
        var baseName = Resources.HighlightDialog_UI_NewGroup_BaseName;
        var name = baseName;
        var uniqueName = false;
        var i = 1;
        while (!uniqueName)
        {
            uniqueName = HighlightGroupList.FindIndex(delegate (HighlightGroup g)
            { return g.GroupName == name; }) < 0;

            if (!uniqueName)
            {
                name = $"{baseName} #{i++}";
            }
        }

        HighlightGroup newGroup = new() { GroupName = name };
        HighlightGroupList.Add(newGroup);
        FillGroupComboBox();
        SelectGroup(HighlightGroupList.Count - 1);
    }

    private void OnBtnOkClick (object sender, EventArgs e)
    {
        // Apply pending changes if closing the form.
        if (IsDirty)
        {
            // cannot call 'this.applyButton.PerformClick();' because it prohibits the OK button to terminate the dialog
            OnBtnApplyClick(btnApply, EventArgs.Empty);
        }
    }

    private void OnChkBoxBoldCheckedChanged (object sender, EventArgs e)
    {
        Dirty();
    }

    private void OnChkBoxNoBackgroundCheckedChanged (object sender, EventArgs e)
    {
        colorBoxBackground.Enabled = !checkBoxNoBackground.Checked;
        btnCustomBackColor.Enabled = !checkBoxNoBackground.Checked;
        Dirty();
    }

    private void OnChkBoxPluginCheckedChanged (object sender, EventArgs e)
    {
        Dirty();
        btnSelectPlugin.Enabled = checkBoxPlugin.Checked;
    }

    private void OnChkBoxRegexMouseUp (object sender, MouseEventArgs e)
    {
        if (e.Button == MouseButtons.Right)
        {
            RegexHelperDialog dlg = new()
            {
                Owner = this,
                CaseSensitive = checkBoxCaseSensitive.Checked,
                Pattern = textBoxSearchString.Text
            };

            if (dlg.ShowDialog() == DialogResult.OK)
            {
                checkBoxCaseSensitive.Checked = dlg.CaseSensitive;
                textBoxSearchString.Text = dlg.Pattern;
            }
        }
    }

    private void OnChkBoxWordMatchCheckedChanged (object sender, EventArgs e)
    {
        Dirty();
        checkBoxNoBackground.Enabled = checkBoxWordMatch.Checked;
    }

    private void OnCmbBoxGroupDrawItem (object sender, DrawItemEventArgs e)
    {
        e.DrawBackground();
        if (e.Index >= 0)
        {
            var group = HighlightGroupList[e.Index];
            Rectangle rectangle = new(0, e.Bounds.Top, e.Bounds.Width, e.Bounds.Height);

            Brush brush = new SolidBrush(SystemColors.ControlText);
            e.Graphics.DrawString(group.GroupName, e.Font, brush, new PointF(rectangle.Left, rectangle.Top));
            e.DrawFocusRectangle();
            brush.Dispose();
        }
    }

    private void OnCmbBoxGroupSelectionChangeCommitted (object sender, EventArgs e)
    {
        SelectGroup(comboBoxGroups.SelectedIndex);
    }

    private void OnCmbBoxGroupTextUpdate (object sender, EventArgs e)
    {
        _currentGroup.GroupName = comboBoxGroups.Text;
    }

    private void OnDeleteButtonClick (object sender, EventArgs e)
    {
        if (listBoxHighlight.SelectedIndex >= 0)
        {
            var removeIndex = listBoxHighlight.SelectedIndex;
            _currentGroup.HighlightEntryList.RemoveAt(removeIndex);
            listBoxHighlight.Items.RemoveAt(removeIndex);

            // Select previous (or first if none before)
            var nextSelectIndex = removeIndex;
            if (nextSelectIndex >= listBoxHighlight.Items.Count)
            {
                nextSelectIndex--; // if last item was removed, go one up
            }

            if (nextSelectIndex >= 0)
            {
                listBoxHighlight.SelectedIndex = nextSelectIndex; // if still some item, select it
            }

            ReEvaluateHighlightButtonStates();
        }
    }

    private void OnHighlightDialogLoad (object sender, EventArgs e)
    {
        colorBoxForeground.SelectedIndex = 1;
        colorBoxBackground.SelectedIndex = 2;
        btnApply.Enabled = false;
        btnApply.Image = null;
        btnBookmarkComment.Enabled = false;
        btnSelectPlugin.Enabled = false;

        ReEvaluateHighlightButtonStates();
    }

    private void OnHighlightDialogShown (object sender, EventArgs e)
    {
        InitData();
    }

    private void OnHighlightListBoxDrawItem (object sender, DrawItemEventArgs e)
    {
        e.DrawBackground();
        if (e.Index >= 0)
        {
            var entry = (HighlightEntry)listBoxHighlight.Items[e.Index];
            Rectangle rectangle = new(0, e.Bounds.Top, e.Bounds.Width, e.Bounds.Height);

            SolidBrush foregroundBrush;

            if (e.State.HasFlag(DrawItemState.Selected))
            {
                foregroundBrush = new SolidBrush(PaintHelper.GetForeColorBasedOnBackColor(entry.ForegroundColor));
            }
            else
            {
                using var backgroundBrush = new SolidBrush(entry.BackgroundColor);
                e.Graphics.FillRectangle(backgroundBrush, rectangle);
                foregroundBrush = new SolidBrush(entry.ForegroundColor);
            }

            using (foregroundBrush)
            {
                e.Graphics.DrawString(entry.SearchText, e.Font, foregroundBrush, new PointF(rectangle.Left, rectangle.Top));
            }

            e.DrawFocusRectangle();
        }
    }

    private void OnListBoxHighlightSelectedIndexChanged (object sender, EventArgs e)
    {
        StartEditEntry();
    }

    private void OnPluginButtonClick (object sender, EventArgs e)
    {
        KeywordActionDlg dlg = new(_currentActionEntry, KeywordActionList);

        if (dlg.ShowDialog() == DialogResult.OK)
        {
            _currentActionEntry = dlg.ActionEntry;
            Dirty();
        }
    }

    #endregion

    #region Private Methods

    private void AddNewEntry ()
    {
        {
            try
            {
                CheckRegex();

                HighlightEntry entry = new()
                {
                    SearchText = textBoxSearchString.Text,
                    ForegroundColor = colorBoxForeground.SelectedColor,
                    BackgroundColor = colorBoxBackground.SelectedColor,
                    IsRegex = checkBoxRegex.Checked,
                    IsCaseSensitive = checkBoxCaseSensitive.Checked,
                    IsLedSwitch = checkBoxDontDirtyLed.Checked,
                    IsStopTail = checkBoxStopTail.Checked,
                    IsSetBookmark = checkBoxBookmark.Checked,
                    IsActionEntry = checkBoxPlugin.Checked,
                    ActionEntry = _currentActionEntry,
                    IsWordMatch = checkBoxWordMatch.Checked,
                    IsBold = checkBoxBold.Checked,
                    NoBackground = checkBoxNoBackground.Checked
                };

                _ = listBoxHighlight.Items.Add(entry);

                // Select the newly created item
                _currentGroup.HighlightEntryList.Add(entry);
                listBoxHighlight.SelectedItem = entry;
            }
            catch (Exception ex) when (ex is ArgumentException
                                            or RegexMatchTimeoutException
                                            or ArgumentNullException
                                            or InvalidOperationException
                                            or SystemException)
            {
                _ = MessageBox.Show(string.Format(CultureInfo.InvariantCulture, Resources.HighlightDialog_UI_ErrorDuringAddOfHighLightEntry, ex.Message),
                    Resources.LogExpert_Common_UI_Title_Error,
                    MessageBoxButtons.OK,
                    MessageBoxIcon.Error);
            }
        }
    }

    private void ChangeToDirty (object sender, EventArgs e)
    {
        Dirty();
    }

    private void CheckRegex ()
    {
        if (checkBoxRegex.Checked)
        {
            if (string.IsNullOrWhiteSpace(textBoxSearchString.Text))
            {
                throw new ArgumentException(Resources.HighlightDialog_RegexError);
            }

            // Use RegexHelper for safer validation with timeout protection
            if (!RegexHelper.IsValidPattern(textBoxSearchString.Text, out var error))
            {
                throw new ArgumentException(error ?? Resources.HighlightDialog_RegexError);
            }
        }
    }

    private static void ChooseColor (ColorComboBox comboBox)
    {
        ColorDialog colorDialog = new()
        {
            AllowFullOpen = true,
            ShowHelp = false,
            Color = comboBox.CustomColor
        };

        if (colorDialog.ShowDialog() == DialogResult.OK)
        {
            comboBox.CustomColor = colorDialog.Color;
            comboBox.SelectedIndex = 0;
        }

        colorDialog.Dispose();
    }

    private void Dirty ()
    {
        var index = listBoxHighlight.SelectedIndex;
        if (index > -1)
        {
            btnApply.Enabled = true;
            btnApply.Image = _applyButtonImage;
        }

        btnAdd.Enabled = textBoxSearchString.Text.Length > 0;
    }

    private void FillGroupComboBox ()
    {
        SelectGroup(-1);

        comboBoxGroups.Items.Clear();

        foreach (var group in HighlightGroupList)
        {
            _ = comboBoxGroups.Items.Add(group);
        }

        ReEvaluateGroupButtonStates();
    }

    private void FillHighlightListBox ()
    {
        listBoxHighlight.Items.Clear();
        if (_currentGroup != null)
        {
            foreach (var entry in _currentGroup.HighlightEntryList)
            {
                _ = listBoxHighlight.Items.Add(entry);
            }
        }
    }

    private void InitData ()
    {
        HighlightGroupList ??= [];

        if (HighlightGroupList.Count == 0)
        {
            HighlightGroup highlightGroup = new()
            {
                GroupName = Resources.HighlightDialog_UI_DefaultGroupName,
                HighlightEntryList = []
            };

            HighlightGroupList.Add(highlightGroup);
        }

        FillGroupComboBox();

        _currentGroup = null;
        var groupToSelect = PreSelectedGroupName;
        if (string.IsNullOrEmpty(groupToSelect))
        {
            groupToSelect = Resources.HighlightDialog_UI_DefaultGroupName;
        }

        foreach (var group in HighlightGroupList)
        {
            if (group.GroupName.Equals(groupToSelect, StringComparison.Ordinal))
            {
                _currentGroup = group;
                comboBoxGroups.SelectedValue = group;
                comboBoxGroups.SelectedIndex = HighlightGroupList.IndexOf(group);
                break;
            }
        }

        ReEvaluateGroupButtonStates();

        FillHighlightListBox();
    }

    private void ReEvaluateGroupButtonStates ()
    {
        // Refresh button states based on the selection in the combobox
        var atLeastOneSelected = comboBoxGroups.SelectedItem != null;
        var moreThanOne = comboBoxGroups.Items.Count > 1;
        var firstSelected = atLeastOneSelected && comboBoxGroups.SelectedIndex == 0;
        var lastSelected = atLeastOneSelected && comboBoxGroups.SelectedIndex == comboBoxGroups.Items.Count - 1;

        btnDeleteGroup.Enabled = atLeastOneSelected;
        btnCopyGroup.Enabled = atLeastOneSelected;
        btnMoveGroupUp.Enabled = atLeastOneSelected && moreThanOne && !firstSelected;
        btnMoveGroupDown.Enabled = atLeastOneSelected && moreThanOne && !lastSelected;
    }

    private void ReEvaluateHighlightButtonStates ()
    {
        // Refresh button states based on the selection in the combobox
        var atLeastOneSelected = listBoxHighlight.SelectedItem != null;
        var moreThanOne = listBoxHighlight.Items.Count > 1;
        var firstSelected = atLeastOneSelected && listBoxHighlight.SelectedIndex == 0;
        var lastSelected = atLeastOneSelected && listBoxHighlight.SelectedIndex == listBoxHighlight.Items.Count - 1;

        btnDelete.Enabled = atLeastOneSelected;
        btnMoveUp.Enabled = atLeastOneSelected && moreThanOne && !firstSelected;
        btnMoveDown.Enabled = atLeastOneSelected && moreThanOne && !lastSelected;
    }

    private void SaveEntry ()
    {
        try
        {
            CheckRegex();

            var entry = (HighlightEntry)listBoxHighlight.SelectedItem;

            entry.ForegroundColor = (Color)colorBoxForeground.SelectedItem;
            entry.BackgroundColor = (Color)colorBoxBackground.SelectedItem;
            entry.SearchText = textBoxSearchString.Text;
            entry.IsRegex = checkBoxRegex.Checked;
            entry.IsCaseSensitive = checkBoxCaseSensitive.Checked;
            btnApply.Enabled = false;
            btnApply.Image = null;
            entry.IsLedSwitch = checkBoxDontDirtyLed.Checked;
            entry.IsSetBookmark = checkBoxBookmark.Checked;
            entry.IsStopTail = checkBoxStopTail.Checked;
            entry.IsActionEntry = checkBoxPlugin.Checked;
            entry.ActionEntry = (ActionEntry)_currentActionEntry.Clone();
            entry.BookmarkComment = _bookmarkComment;
            entry.IsWordMatch = checkBoxWordMatch.Checked;
            entry.IsBold = checkBoxBold.Checked;
            entry.NoBackground = checkBoxNoBackground.Checked;
            listBoxHighlight.Refresh();
        }
        catch (Exception ex) when (ex is ArgumentException
                                        or RegexMatchTimeoutException
                                        or ArgumentNullException
                                        or InvalidOperationException
                                        or SystemException)
        {
            _ = MessageBox.Show(string.Format(CultureInfo.InvariantCulture, Resources.HighlightDialog_UI_ErrorDuringSavingOfHighlightEntry, ex.Message), Resources.LogExpert_Common_UI_Title_Error);
        }
    }

    private void SelectGroup (int index)
    {
        if (index >= 0 && index < HighlightGroupList.Count)
        {
            _currentGroup = HighlightGroupList[index];
            comboBoxGroups.Items[index] = _currentGroup;
            comboBoxGroups.SelectedIndex = index;
            comboBoxGroups.SelectedItem = _currentGroup;
            FillHighlightListBox();
        }
        else
        {
            comboBoxGroups.SelectedItem = null;
            _currentGroup = null;
            listBoxHighlight.Items.Clear();
        }

        ReEvaluateHighlightButtonStates();
        ReEvaluateGroupButtonStates();
    }

    private void StartEditEntry ()
    {
        var entry = (HighlightEntry)listBoxHighlight.SelectedItem;

        if (entry != null)
        {
            textBoxSearchString.Text = entry.SearchText;

            colorBoxForeground.CustomColor = entry.ForegroundColor;
            colorBoxBackground.CustomColor = entry.BackgroundColor;

            if (colorBoxForeground.Items.Contains(entry.ForegroundColor))
            {
                colorBoxForeground.SelectedIndex = colorBoxForeground.Items.Cast<Color>().ToList().LastIndexOf(entry.ForegroundColor);
            }
            else
            {
                colorBoxForeground.SelectedItem = entry.ForegroundColor;
            }

            if (colorBoxForeground.Items.Contains(entry.ForegroundColor))
            {
                colorBoxBackground.SelectedIndex = colorBoxBackground.Items.Cast<Color>().ToList().LastIndexOf(entry.BackgroundColor);
            }
            else
            {
                colorBoxBackground.SelectedItem = entry.BackgroundColor;
            }

            checkBoxRegex.Checked = entry.IsRegex;
            checkBoxCaseSensitive.Checked = entry.IsCaseSensitive;
            checkBoxDontDirtyLed.Checked = entry.IsLedSwitch;
            checkBoxBookmark.Checked = entry.IsSetBookmark;
            checkBoxStopTail.Checked = entry.IsStopTail;
            checkBoxPlugin.Checked = entry.IsActionEntry;
            btnSelectPlugin.Enabled = checkBoxPlugin.Checked;
            btnBookmarkComment.Enabled = checkBoxBookmark.Checked;
            _currentActionEntry = entry.ActionEntry != null ? (ActionEntry)entry.ActionEntry.Clone() : new ActionEntry();
            _bookmarkComment = entry.BookmarkComment;
            checkBoxWordMatch.Checked = entry.IsWordMatch;
            checkBoxBold.Checked = entry.IsBold;
            checkBoxNoBackground.Checked = entry.NoBackground;
        }

        btnApply.Enabled = false;
        btnApply.Image = null;

        ReEvaluateHighlightButtonStates();
    }

    #endregion
}
